/**
 * 
 */
package vue.popup;

import java.awt.Window;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.util.HashMap;
import java.util.Map;

import javax.swing.BorderFactory;
import javax.swing.BoxLayout;
import javax.swing.JButton;
import javax.swing.JComboBox;
import javax.swing.JDialog;
import javax.swing.JPanel;

import model.preprocessor.EPreProcessor;
import model.preprocessor.PreProcessorFactory;
import model.session.CNFUse;
import controller.ISessionManager;
import controller.preprocessor.Hypre;
import controller.preprocessor.PreProcessor;
import controller.preprocessor.ReViVal;
import controller.preprocessor.SatEllite1_0;

/**
 * A dialog to choose a preprocessor, set the parameter and lunch it.
 * 
 * @author GRONOWSKI Stephane svan001@aol.com
 * 
 *         igsat 2010
 * 
 */
public class IGPreprocessorDialog extends JDialog implements ActionListener, KeyListener {
	private static final long						serialVersionUID			= 1L;
	public static final String						TITLE						= "Preprocessor execution dialog";
	public static final String						RUN_MESSAGE					= "RUN !!";
	public static final String						COMBO_TITLE					= "Choose preprocessor";
	public static final int							PARAMETER_DIALOG_POSITION	= 1;

	private ISessionManager							manager;
	private CNFUse									cnf;

	// private Set<ESolver> availableDialogSolver = new HashSet<ESolver>();
	private Map<PreProcessor, IGDialogParameter>	dialogsParameters			= new HashMap<PreProcessor, IGDialogParameter>();

	private PreProcessor							selected					= null;

	private JComboBox								comboBox;
	private JButton									run;
	private JPanel									panel;


	/**
	 * Create {@link IGPreprocessorDialog}.
	 * 
	 * @param manager
	 *            {@link ISessionManager} of the session
	 * @param cnf
	 *            {@link CNFUse} concern by the execution
	 * @param owner
	 *            window owner of the dialog
	 * @param first
	 *            the default choice
	 */
	public IGPreprocessorDialog(ISessionManager manager, CNFUse cnf, Window owner, EPreProcessor first) {
		super(owner, TITLE);

		this.manager = manager;
		this.cnf = cnf;
		initDialogsParamater(first);

		panel = new JPanel();
		panel.setLayout(new BoxLayout(panel, BoxLayout.Y_AXIS));
		setContentPane(panel);


		// comboBox
		comboBox = new JComboBox(dialogsParameters.keySet().toArray());
		comboBox.setBorder(BorderFactory.createTitledBorder(COMBO_TITLE));
		comboBox.addActionListener(this);

		panel.add(comboBox);

		// preprocessor
		panel.add(dialogsParameters.get(selected));
		comboBox.setSelectedItem(selected);


		// bouton
		run = new JButton(RUN_MESSAGE);
		// run.setEnabled(false);
		run.setAlignmentX(JButton.RIGHT_ALIGNMENT);
		run.addActionListener(this);

		panel.add(run);

		addKeyListener(this);

		// ouai je sais
		setFocusable(true);
		requestFocusInWindow();
		getContentPane().requestFocus();

		setDefaultCloseOperation(JDialog.DISPOSE_ON_CLOSE);
		pack();

	}

	/**
	 * Initialise the different {@link IGDialogParameter} for each solver.
	 ** 
	 * @param first
	 *            the preproc selected selection, null if no default choice
	 */
	private void initDialogsParamater(EPreProcessor first) {
		PreProcessorFactory fact = manager.getPreProcessorFactory();
		PreProcessor preproc = null;
		IGDialogParameter dialog = null;

		for (EPreProcessor s : manager.getAvailablePreProcessor())
		{
			try
			{
				switch (s) {
				case HYPRE:
					Hypre hypre = fact.createHyprePreProcessor();
					if (hypre == null)
						break;
					preproc = hypre;
					dialog = new IGHypreDialogParameter(hypre.getHypreParameter());
					break;
				case REVIVAL:
					ReViVal rev = fact.createRevivalPreProcessor();
					if (rev == null)
						break;
					preproc = rev;
					dialog = new IGRevivalDialogParameter(rev.getRevivalParameter());
					break;
				case SATELLITE_1_0:
					SatEllite1_0 sat = fact.createSatellitePreProcessor();
					if (sat == null)
						break;
					preproc = sat;
					dialog = new IGSatelliteDialogParameter(sat.getSatelliteParameter());
					break;

				default:
					preproc = null;
				}
			} catch (Exception e)
			{
				e.printStackTrace();
				preproc = null;
			}
			if (preproc == null || dialog == null)
				continue;

			dialogsParameters.put(preproc, dialog);
			if (first == s)
				selected = preproc;
		}

		if (selected == null)
			selected = (PreProcessor) dialogsParameters.keySet().toArray()[0];
	}

	@Override
	public void actionPerformed(ActionEvent e) {
		if (e.getSource() == comboBox)
		{// change the solverParameter
			selected = (PreProcessor) comboBox.getSelectedItem();
			panel.remove(PARAMETER_DIALOG_POSITION);
			panel.add(dialogsParameters.get(selected), PARAMETER_DIALOG_POSITION);
			pack();
			return;
		}

		if (e.getSource() == run)
		{
			System.out.println("confirme run");

			if (dialogsParameters.get(selected).checkAndSetParameter())
			{
				System.out.println("execute preproc");
				manager.executePreProcessor(selected, cnf);
				dispose();
			}
			else
				pack();
			return;
		}
	}

	@Override
	public void keyPressed(KeyEvent e) {
		if (e.getKeyCode() == KeyEvent.VK_ENTER)
			run.doClick();
	}

	@Override
	public void keyReleased(KeyEvent e) {
		// rien
	}

	@Override
	public void keyTyped(KeyEvent e) {
		// rien
	}


}
